﻿#pragma once
#include <unordered_map>
#include "base/core/singleton.h"
#include "base/core/object_pool.h"
#include "Active/ActiveCharacter.h"
#include "ICharacterObserver.h"
#include "Common/Timer/TimerAxis.h"
#include "ProtoBuffer/AllProtocol.h"

using namespace ProtoBuf;

class ActiveCharacterMgr : public ITimerHandler, public ManualSingleton<ActiveCharacterMgr>
{
	friend class ManualSingleton<ActiveCharacterMgr>;

	enum class EACTIVE_MGR
	{
		TIMER_ID_CHECK_ACTIVE_DATA = 1,						//检查活跃数据定时器ID
		TIMER_ID_CHECK_ACCOUNT_TOKEN_EXPIRE = 2,			//检查在线账户token过期时间
		MAX_ACTIVE_CHARACTER_SAVE_TIME = (7*24*3600),		//活跃数据保存最长时间
	};
protected:
	//活跃角色map
	typedef std::unordered_map<CharIDType, ActiveCharacter*> ACTIVE_CHARACTER_MAP;
	//在线角色map
	typedef std::unordered_map<CharIDType, ActiveCharacter*> ONLINE_CHARACTER_MAP;
	//观察者列表
	typedef std::list<ICharacterObserver*> CHARACTER_OBSERVER_LIST;


	//角色观察者列表
	CHARACTER_OBSERVER_LIST m_CharacterObserverList;
	//活跃角色对象池
	ObjectPool<ActiveCharacter>*m_pActiveCharacterPool;
	//活跃角色map
	ACTIVE_CHARACTER_MAP    m_ActiveCharacterMap;
	//在线角色map
	ONLINE_CHARACTER_MAP	m_OnlineCharacterMap;

public:
    bool            Init();
    bool            UnInit();
    bool            Update(uint64_t tick);

	//定时器回调
	virtual void OnTimer(uint32_t nTimerID);
	//角色登录
	bool OnCharacterLogin(CenterLoginLogicRsp &enter,uint32_t channelId);
	//角色下线
	bool OnCharacterLogout(CharIDType charID);
	//删除角色
	bool OnCharacterDel(CharIDType charID);
	//角色更新
	void OnCharacterUpdate(LogicToCenterCharSync &charSync);
	//角色外观更新
	void OnCharacterFacadeUpdate(LogicToCenterCharFacadeSync &facade);
	//角色切换场景
	void OnCharacterChangeScene(CharIDType cid, uint32_t sceneId, uint32_t mapId, Point3<float> pos);
	//角色断开连接
	void OnCharacterDisconnect(CharIDType charID);
	//角色重连
	void onCharacterReconnect(CharIDType charID);
	//增加观察者
	bool AddCharacterObserver(ICharacterObserver *pCharacterObserver);
	//移除观察者
	bool RemoveCharacterObserver(ICharacterObserver *pCharacterObserver);

	//获取在线角色
	ActiveCharacter*	GetOnlineCharacter(CharIDType id);
	//获取活跃角色
	ActiveCharacter*	GetActiveCharacter(CharIDType id);
	//添加一个活跃玩家数据
	bool  AddActiveCharacter(const ActiveCharacterDBInfo &info);
	//获取一个活跃角色对象
	ActiveCharacter*	MakeActiveCharacter();
	//回收一个活跃角色对象
	bool				FreeActiveCharacter(ActiveCharacter* activeCharacter);
	//获取在线人数
	uint32_t			GetOnlineNum();
	//返回在线的玩家列表
	ONLINE_CHARACTER_MAP& GetOnlineCharacterMap();

protected:
	//检查所有活跃数据
	void CheckActiveCharacter();
	//清空所有在线账户
	bool			_ClearAllOnlineAccount();
	//检查在线账户的登录token过期时间
	bool            _CheckOnlineAccountTimeout();
	//清空所有在线角色
	bool _ClearAllActiveCharacter();

	ActiveCharacterMgr();
	virtual ~ActiveCharacterMgr();
};

#define g_MakeActiveCharacterMgr() (ActiveCharacterMgr::Instance())
#define g_GetActiveCharacterMgr()  (ActiveCharacterMgr::GetInstance())
#define g_DelActiveCharacterMgr()  (ActiveCharacterMgr::Destroy())
